package com.wrupple.muba.common.domain;

import java.io.Serializable;
import java.util.HashMap;
import java.util.Map;

import com.google.gwt.core.client.JavaScriptObject;
import com.google.gwt.place.shared.Place;
import com.google.gwt.user.client.rpc.IsSerializable;

/**
 * 
 * An Application's Atomic Unit of User Interaction. It holds the information to
 * start an element inside the application and allow the user to start working
 * 
 * The unique identifier, while recommended to be a
 * no-spaces-no-special-characters String, no actual checks will be done on
 * runtime to assert it.
 * 
 * 
 * @author japi
 * 
 */
public class DesktopPlace extends Place implements Serializable,
		IsSerializable {
	
	public static final String IMAGE_PARAMETER = "image";
	public static final String LABEL_PARAMETER = "name";
	public static final String CATALOG = "DesktopPlace";

	private static final long serialVersionUID = -7689056368151452282L;

	private String activity;

	private Map<String, String> properties;
	
	/**
	 * a descriptor of this place in the application hierarchy
	 */
	private JavaScriptObject applicationItem;

	/**
	 * Creates a new ApplicationItem
	 */
	public DesktopPlace() {
		super();
		this.properties = new HashMap<String, String>();
	}
	
	public DesktopPlace(DesktopPlace place) {
		super();
		this.activity=place.getActivity();
		setProperties(place.getProperties());
	}

	public DesktopPlace(String place) {
		this();
		this.activity = place;
	}

	/**
	 * @return machine-readable (no sapaces/special characters allowed) Unique
	 *         identifier for this Item
	 */
	public String getActivity() {
		return activity;
	}

	/**
	 * @param id
	 *            machine-readable (no sapaces/special characters allowed)
	 *            Unique identifier for this Item
	 */
	public void setActivity(String id) {
		this.activity = id;
	}


	/**
	 * Propperties plugins will look for when the item gets called
	 * 
	 * @param name
	 *            name of the propperty
	 * @return Propperty a String value
	 */
	public String getProperty(String name) {
		return this.properties.get(name);
	}

	/**
	 * @param name
	 *            name of the propperty
	 * @param value
	 *            value of the propperty
	 * @return
	 */
	public String getProperty(String name, String value) {
		return this.properties.put(name, value);
	}

	/**
	 * @return the map of properties
	 */
	public Map<String, String> getProperties() {
		return properties;
	}

	/**
	 * @param map
	 *            of properties the properties to set
	 */
	public void setProperties(Map<String, String> properties) {
		this.properties = properties;
	}

	public void setProperty(String name, String value) {
		this.properties.put(name, value);
	}

	public DesktopPlace copyWithoutProperties() {
		DesktopPlace item = new DesktopPlace();
		item.setActivity(new String(activity));
		return item;
	}

	public DesktopPlace cloneItem() {
		DesktopPlace item = copyWithoutProperties();
		item.setProperties(new HashMap<String, String>(properties));
		return item;
	}

	public void removeProperty(String key) {
		properties.remove(key);
	}

	/* (non-Javadoc)
	 * @see java.lang.Object#hashCode()
	 */
	@Override
	public int hashCode() {
		final int prime = 31;
		int result = 1;
		result = prime * result
				+ ((activity == null) ? 0 : activity.hashCode());
		result = prime * result
				+ ((properties == null) ? 0 : properties.hashCode());
		return result;
	}

	/* (non-Javadoc)
	 * @see java.lang.Object#equals(java.lang.Object)
	 */
	@Override
	public boolean equals(Object obj) {
		if (this == obj)
			return true;
		if (obj == null)
			return false;
		if (getClass() != obj.getClass())
			return false;
		DesktopPlace other = (DesktopPlace) obj;
		if (activity == null) {
			if (other.activity != null)
				return false;
		} else if (!activity.equals(other.activity))
			return false;
		if (properties == null) {
			if (other.properties != null)
				return false;
		} else if (!properties.equals(other.properties))
			return false;
		return true;
	}

	public String getImage(){
		return getProperty(IMAGE_PARAMETER);
	}
	
	public void setImage(String image){
		setProperty(IMAGE_PARAMETER, image);
	}
	
	public String getName(){
		return getProperty(LABEL_PARAMETER);
	}

	public void setName(String value) {
		setProperty(LABEL_PARAMETER, value);
	}

	public JavaScriptObject getApplicationItem() {
		return applicationItem;
	}

	public void setApplicationItem(JavaScriptObject applicationItem) {
		this.applicationItem = applicationItem;
	}
	

}